using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using DG.Tweening;
using UnityEngine.UI;
using Yoozoo.UI.YGUI;

namespace com.yoozoo.gta.Art.BeautyGirl
{
    public class ChangeClothTool : MonoBehaviour
    {
        [Header("衣服变量和变暗分别持续时间")][SerializeField] public float effectDuration = 0.5f; // 衣服变亮效果的持续时间
        [Header("皮肤切换特效")][SerializeField] public GameObject clothChangeEffect; // 新皮肤出现时播放的爱心特效预制体
        [Header("皮肤选择按钮的父级")][SerializeField] public RectTransform rectTransform; // 皮肤更换菜单的父节点
        [Header("皮肤选择按钮预制体")][SerializeField] public GameObject materialMenuOptions; // 皮肤更换菜单的选项预制体
        [Header("可更换的皮肤模型")][SerializeField] public GameObject[] clothList; // 当前角色所拥有的所有皮肤列表

        [SerializeField] private Material currentClothMaterial; // 当前皮肤的材质
        [SerializeField] private Material dstClothMaterial; // 目标皮肤的材质
        [SerializeField] private GameObject instanceClothChangeEffect; // 当前播放的爱心特效实例
        [SerializeField] private ParticleSystem clothChangeEffectSys; // 当前播放的爱心特效系统
        [SerializeField] private int _currIdx = 0; // 当前皮肤在皮肤列表中的索引
        [SerializeField] private int _dstIdx = 0; // 目标皮肤的索引
        
        [SerializeField] private List<YButton> buttons = new List<YButton>(); // 皮肤更换菜单的按钮列表
        
        private Coroutine destroyCoroutine;
        private void Start()
        {
            for (int i = 0; i < clothList.Length; i++)
            {
                clothList[i].SetActive(i == _currIdx);
            }
            InitButton();
        }

        /// <summary>
        /// 设置皮肤数据
        /// </summary>
        /// <param name="currIdx">当前皮肤索引</param>
        /// <param name="clothList">皮肤列表</param>
        /// <param name="clothChangeEffect">皮肤更换特效</param>
        public void SetClothDate(int currIdx, GameObject[] clothList, GameObject clothChangeEffect)
        {
            this.clothList = clothList;
            _currIdx = currIdx;
            
            for (int i = 0; i < clothList.Length; i++)
            {
                clothList[i].SetActive(i == _currIdx);
            }
        }

        public void ChangeCloth(int index)
        {
            _dstIdx = index;
            if (index < 0 || index >= clothList.Length || index == _currIdx || clothChangeEffect == null)
            {
                Debug.LogWarning("Index out of range or same index or clothChangeEffect is null");
                return;
            }
            
            currentClothMaterial = clothList[_currIdx].GetComponent<SkinnedMeshRenderer>().material;
            dstClothMaterial = clothList[_dstIdx].GetComponent<SkinnedMeshRenderer>().material;
            if (destroyCoroutine != null) StopCoroutine(destroyCoroutine);
            // 防止快速切换皮肤导致出现大量残留粒子系统
            if (instanceClothChangeEffect == null)
            {
                instanceClothChangeEffect = Instantiate(clothChangeEffect, clothList[_dstIdx].transform.parent);
            }
            clothChangeEffectSys = instanceClothChangeEffect.GetComponent<ParticleSystem>();
            
            if (currentClothMaterial == null || dstClothMaterial == null)
            {
                Debug.LogError("Material not found");
                return;
            }

            // 玩家切换皮肤时，当前皮肤先变亮的效果
            currentClothMaterial.DOFloat(1.0f, "_ClothChangeValue", effectDuration).OnComplete(() =>
            {
                ChangeClothActive(index);
            });
            _currIdx = index;
        }

        private void ChangeClothActive(int index)
        {
            // Debug.LogError("ChangingClothActive: " + index);
            // 切换皮肤，当前皮肤和其余皮肤隐藏，目标皮肤显示
            for (int i = 0; i < clothList.Length; i++)
            {
                clothList[i].SetActive(i == index);
            }
            // 播放爱心特效
            clothChangeEffectSys.Play(true);
            // 目标皮肤出现的那一刻是发亮的，慢慢地恢复成正常的衣服效果
            dstClothMaterial.SetFloat("_ClothChangeValue", 1.0f);
            dstClothMaterial.DOFloat(0.0f, "_ClothChangeValue", effectDuration).OnComplete(() =>
                {
                    // 特效播放完毕后销毁
                    destroyCoroutine = StartCoroutine(DestroyAfterDelay(instanceClothChangeEffect, clothChangeEffectSys.main.duration-effectDuration));
            });

            currentClothMaterial.SetFloat("_ClothChangeValue", 0);
        }
        
        private IEnumerator DestroyAfterDelay(GameObject obj, float delay)
        {
            yield return new WaitForSeconds(delay);
            if(clothChangeEffectSys.isStopped)
            {
                Destroy(obj);
            }
            
        }

        private void InitButton()
        {
            int ClothsCount = clothList.Length;
            int ClothsGroups = ClothsCount / 2;
            //取余
            int ClothsRemainder = ClothsCount % 2;
            
            for (int i = 0; i < ClothsGroups; i++)
            {
                GameObject instClothsGroup = Instantiate(materialMenuOptions, rectTransform);
                buttons.AddRange(instClothsGroup.GetComponentsInChildren<YButton>());
            }
            if(ClothsRemainder > 0)
            {
                GameObject instClothsGroup = Instantiate(materialMenuOptions, rectTransform);
                buttons.Add(instClothsGroup.GetComponentsInChildren<YButton>()[0]);
                Destroy(instClothsGroup.GetComponentsInChildren<YButton>()[1].transform.parent.gameObject);
            }
            
            for (int i = 0; i < buttons.Count; i++)
            {
                int index = i;
                buttons[i].onClick.AddListener(() => ChangeCloth(index));
                buttons[i].GetComponentInChildren<Text>().text = "皮肤 " + i;
                buttons[i].GetComponentInChildren<Text>().name = "皮肤 " + i;
            }
        }
        
        /// <summary>
        /// 清理资源
        /// </summary>
        private void OnClear()
        {
            if (instanceClothChangeEffect != null)
            {
                Destroy(instanceClothChangeEffect);
            }
            
            instanceClothChangeEffect = null;
            currentClothMaterial = null;
            dstClothMaterial = null;
            clothChangeEffectSys = null;
        }

        private void OnDestroy()
        {
            OnClear();
        }
        private void OnDisable()
        {
            OnClear();
        }
    }
}